package com.sumainfor.pc.gmio.service.impl;
import com.sumainfor.common.config.RedisUtils;
import com.sumainfor.common.entity.TemplateData;
import com.sumainfor.common.util.*;
import com.sumainfor.common.utlis.*;
import com.sumainfor.common.wechat.WeChatConfig;
import com.sumainfor.pc.gmio.dao.DiWithdrawalMapper;
import com.sumainfor.pc.gmio.dao.HoTenantBillMapper;
import com.sumainfor.pc.gmio.dao.UtilsMapper;
import com.sumainfor.pc.gmio.feign.Zfeign.ZpcMktFeign;
import com.sumainfor.pc.gmio.service.DiWithdrawalService;
import net.sf.json.JSONObject;
import org.apache.commons.collections.MapUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.interceptor.TransactionAspectSupport;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.locks.ReentrantLock;

/**
 * 退租账单
 */
@Service
public class DiWithdrawalSerivceImpl implements DiWithdrawalService {

    private ReentrantLock lock = new ReentrantLock(false);
    Logger log = LoggerFactory.getLogger(DiWithdrawalSerivceImpl.class);
    @Autowired
    private DiWithdrawalMapper diWithdrawalMapper;
    @Autowired
    private ZpcMktFeign zpcMktFeign;
    @Autowired
    private UtilsMapper utilsMapper;
    @Autowired
    private HoTenantBillMapper hoTenantBillMapper;
    @Autowired
    private RedisUtils redisUtils;
    String UUID = null;

    /*
     * 查询账单列表
     * */
    @Override
    public JsonResult getWithdrawalList(Map<String, Object> params, Pager pager) {
        List<Map<String,Object>> HouInfoList=new ArrayList<>();
        //是否有选择省市区条件
        if (!params.get("Province").toString().equals("")
                ||  !params.get("City").toString().equals("")
                ||  !params.get("District").toString().equals("")
                ||  !params.get("Street").toString().equals("")
                ||  !params.get("ComId").toString().equals("")
                ||  !params.get("BuilDing").toString().equals("")
                ||  !params.get("Room").toString().equals("")

        ){
//            JsonResult comFeign=zpcMktFeign.getComIdList(params);
//            if (comFeign.get("errorCode").equals("0")) {
//                comlist=(List<Map<String,Object>>)comFeign.get("result");
//                params.put("comlist",comlist);
//            }

            JsonResult comFeign=zpcMktFeign.getHouInfoList(params);
            if (comFeign.get("errorCode").equals("0")) {
                HouInfoList=(List<Map<String,Object>>)comFeign.get("result");
                params.put("HouInfoList",HouInfoList);
            }


        }
        PageUtils pageUtils = new PageUtils();
        pager.setPagerNecessary(params, pager);
        Integer cout = diWithdrawalMapper.getWithdrawalListCount(params);
        if (cout == 0) {
            return pageUtils.getJsonResult(new ArrayList<Map<String, Object>>(), params, cout);
        }
        List<Map<String, Object>> getCommunityList = diWithdrawalMapper.getWithdrawalList(params);
        List<String> idList = new ArrayList<String>();
        List<String> tList=new ArrayList<String>();
        for (Map<String, Object> map : getCommunityList) {
            if (map.get("HouInfoId") != null) {
                idList.add(map.get("HouInfoId").toString());
            }
            if(map.get("TenId")!=null){
                tList.add(map.get("TenId").toString());
            }
        }
        params.put("idList", idList);//房源编号
        params.put("TenantList",tList);//租客编号
        JsonResult result = zpcMktFeign.getHouInfoListForDbill(params);
        System.out.println("市场部返回的数据:"+result);
        if (result.get("errorCode").equals("0")) {
            Map<String,Object> maktMap=(Map<String,Object>)result.get("result");
            List<Map<String, Object>> mktList = (List<Map<String, Object>>) maktMap.get("list");
            List<Map<String, Object>> tenList = (List<Map<String, Object>>) maktMap.get("tList");
            System.out.println("tenList:"+tenList);
            int count = 0;
            for (Map<String, Object> map : mktList) {
                for (Map<String, Object> map2 : getCommunityList) {
                    if (MapUtils.getString(map, "HouInfoId").equals(MapUtils.getString(map2, "HouInfoId"))) {
                        map2.putAll(map);
                    }
                }
            }
            for (Map<String, Object> map : tenList) {
                for (Map<String, Object> map2 : getCommunityList) {
                    if (MapUtils.getString(map, "TenId").equals(MapUtils.getString(map2, "TenId"))) {
                        map2.putAll(map);
                    }
                }
            }
            return pageUtils.getJsonResult(getCommunityList, params, cout);

        }
        return result; }
    /**
     * 租后主管审核退租
     */
    @Transactional(rollbackFor = Exception.class)
    public JsonResult updateWithdrawal(Map<String,Object> params){
        JsonResult result=new JsonResult();
        /**
         * 加锁操作
         */
        lock.lock();
        try{
            try {
                if (params.get("WitId")==
                        null || params.get("openid")==null || params.get("ComName")==null
                        || params.get("Address")==null || params.get("PaId")==null|| params.get("ProOperaType")==null
                        || params.get("HouId")==null || params.get("HouInfoId")==null || params.get("DelIdList")==null
                        || params.get("InteDeviceList")==null ||params.get("ifIntelligentDevice")==null || params.get("inteType")==null
                        || params.get("WitType")==null){
                    return result.putFailed("参数不正确");
                }
                params.put("by", ContextUtils.getUserId());//操作人
                params.put("term", "4");// 创建端 Insert端： 1 租客端 2市场部 3 工程部   4运营部   5财务部  6总经办 7发展部
                params.put("fnc",
                        this.getClass().getSimpleName() + "." + Thread.currentThread().getStackTrace()[1].getMethodName());// 创建Function名
                ParamsCommon.commonUpdateParms(params);
                params.put("AuditTime",params.get("instm"));//审核时间
                params.put("AuditId",ContextUtils.getUserId());//审核人编号
                Integer count=diWithdrawalMapper.updateWithdrawal(params);
                //智能设备供应商     0 无智能门锁   2.科技侠   3.果加
                if (params.get("inteType").toString().equals("2") || params.get("inteType").toString().equals("3")){
                    //需要删除密码的数据（删除蓝牙密钥）
                    List<Map<String,Object>> lockList=(List<Map<String,Object>>)params.get("DelIdList");
                    //保存钥匙编号（传递到市场部修改内部系统钥匙信息）
                    List<String> smaIdList=new ArrayList<String>();
                    System.out.println("lockList:"+lockList);
                    String DeviceLockToken="";//科技侠的登录token
                    String GuoJiaToken="";//果加的登录token
                    if (params.get("inteType").toString().equals("2")){//获取科技侠的登录token
                        DeviceLockToken=redisUtils.get("DeviceLockToken");
                        //如果获取不到就重新登录
                        if (DeviceLockToken==null){
                            Map<String,Object> tokenMap=new HashMap<String, Object>();
                            tokenMap.put("client_id",InteDeviceLockConfig.CLIENT_ID);
                            tokenMap.put("client_secret",InteDeviceLockConfig.CLIENT_SECRET);
                            tokenMap.put("grant_type",InteDeviceLockConfig.GRANT_TYPE_PASSWORD);
                            tokenMap.put("username",InteDeviceLockConfig.USERNAME);
                            tokenMap.put("password",InteDeviceLockConfig.PASSWORD);
                            tokenMap.put("redirect_uri",InteDeviceLockConfig.REDIRECT_URL);
                            System.out.println("请求科技侠的参数:"+tokenMap);
                            tokenMap=InteDeviceLockUtil.oauth2Token(tokenMap);
                            if (tokenMap.get("access_token")!=null){
                                DeviceLockToken=tokenMap.get("access_token").toString();
                                //token存到redis中
                                redisUtils.set("DeviceLockToken",DeviceLockToken,Long.valueOf(tokenMap.get("expires_in").toString()));
                            }else{
                                return result.putFailed("token获取失败");
                            }
                            Map<String,Object> lockMap=new HashMap<String,Object>();
                            lockMap.put("clientId", InteDeviceLockConfig.CLIENT_ID);
                            lockMap.put("accessToken",DeviceLockToken);
                            int lockNum=0;//保存删除成功的
                            for(Map<String,Object> map :lockList){
                                smaIdList.add(map.get("SmaId").toString());//钥匙编号
                                //智能设备供应商     2.科技侠   3.果加
                                //密码类型   1.键盘密码  2.蓝牙密码
                                if (map.get("CodeType").toString().equals("2")){
                                    lockMap.put("keyId",map.get("CodeId"));//密码id
                                    lockMap.put("date", InteDeviceLockUtil.getTimeSign());
                                    Map<String,Object> inteMap=InteDeviceLockUtil.keyDelete(lockMap);
                                    if(inteMap.get("errcode").toString().equals("0")){
                                        lockNum++;
                                    }
                                }
                            }
                        }
                    }else if(params.get("inteType").toString().equals("3")) {//获取果加的登录token
                        GuoJiaToken=redisUtils.get("GuoJiaToken");
                        //如果获取不到就重新登录
                        if (GuoJiaToken==null){
                            Map<String,Object> guoJiaMap=new HashMap<String, Object>();
                            guoJiaMap.put("s_id",InteGuoJiaUtil.getSid());
                            guoJiaMap.put("version","1");
                            com.alibaba.fastjson.JSONObject bodyJson=new com.alibaba.fastjson.JSONObject();
                            //key
                            DESEncrypt desPlus2 = new DESEncrypt(InteGuoJiaConfig.DES_KEY);
                            //密码
                            bodyJson.put("account",InteGuoJiaConfig.ACCOUNT);
                            bodyJson.put("password",desPlus2.encrypt(InteGuoJiaConfig.PASSWORD));
                            guoJiaMap=InteGuoJiaUtil.login(guoJiaMap,bodyJson);
                            if (guoJiaMap.get("rlt_code") !=null && guoJiaMap.get("rlt_code").toString().equals("HH0000")){//HH0000 、成功
                                //返回的token数据
                                Map<String,Object>dataMap=(Map<String,Object>)guoJiaMap.get("data");
                                GuoJiaToken=dataMap.get("access_token").toString();
                                //token存到redis中
                                redisUtils.set("GuoJiaToken",GuoJiaToken,Long.valueOf(dataMap.get("expires_second").toString()));
                            }else{
                                return result.putFailed("token获取失败");
                            }
                        }
                        /*解除对用户的门锁授权*/
                        Map<String,Object> lockMap=new HashMap<String, Object>();
                        lockMap.put("s_id",InteGuoJiaUtil.getSid());
                        lockMap.put("version","1");
                        lockMap.put("access_token",GuoJiaToken);
                        com.alibaba.fastjson.JSONObject bodyJson=new com.alibaba.fastjson.JSONObject();
                        int lockNum=0;//保存删除成功的
                        for(Map<String,Object> map :lockList){
                            smaIdList.add(map.get("SmaId").toString());//钥匙编号
                            //智能设备供应商     2.科技侠   3.果加
                            bodyJson.put("lock_no",map.get("CodeId"));//这里相当于果加的智能设备编号
                            bodyJson.put("mobile",map.get("Code"));//这里相当于果加用户的手机号
                            System.out.println("果加传递lockMap:"+lockMap);
                            System.out.println("果加传递bodyJson:"+bodyJson);
                            Map<String,Object> inteMap=InteGuoJiaUtil.lockCancel_auth(lockMap,bodyJson);
                            System.out.println("果加返回inteMap:"+inteMap);
                            if(inteMap.get("rlt_code")!=null && inteMap.get("rlt_code").toString().equals("HH0000")){
                                lockNum++;
                            }
                        }
                    }
                    //把已删除的智能钥匙编号传递到市场部
                    params.put("smaIdList",smaIdList);
                    //WitType 退租账单类型   1.租客违约   2.唐巢违约（唐巢违约不需要违约金）3租客正常退
                    //Withdrawal 退租状态   0.正常退租    1.强制退   2.违约退
                    if (String.valueOf(params.get("WitType")).equals("1")){
                        params.put("Withdrawal","2");
                    }else if (String.valueOf(params.get("WitType")).equals("3")){
                        params.put("Withdrawal","0");
                    }

                }
                if (count>0 ){
                    //智能电表的数组
                    List<Map<String,Object>> InteDeviceList=(List<Map<String,Object>>)params.get("InteDeviceList");
                    //如果智能电表数组不为空的就去执行大华or蜂电的退租操作
                    if (InteDeviceList.size()>0){
                        //智能设备供应商     0.蜂电   1.大华   2.科技侠   3.果加
                        if (params.get("ifIntelligentDevice").toString().equals("0")){
                            String InteDeviceBeeToken=redisUtils.get("InteDeviceBeeToken");
                            //如果获取不到就重新登录
                            if (InteDeviceBeeToken==null) {
                                Map<String, Object> tokenMap = new HashMap<String, Object>();
                                params.put("version","0116010101");//版本号 默认 0116010101
                                params.put("appid", InteDeviceBeeConfig.APP_ID);
                                tokenMap=InteDeviceBeeUtil.userLogin(InteDeviceBeeConfig.USERID, InteDeviceBeeConfig.PASS,params);
                                if (tokenMap.get("Code").toString().equals("0")) {
                                    InteDeviceBeeToken = tokenMap.get("Expand").toString();
                                    //token存到redis中 有效时长一个小时
                                    redisUtils.set("InteDeviceBeeToken", InteDeviceBeeToken,3600);
                                } else {
                                    return result.putFailed("token获取失败");
                                }
                            }
                            //蜂电接口请求头必传的参数
                            Map<String,Object> headMap=new HashMap<String,Object>();
                            headMap.put("uid",InteDeviceBeeConfig.UID);
                            headMap.put("token",InteDeviceBeeToken);
                            if (params.get("ProOperaType").toString().equals("1")) {//租赁类型（1.合租 2.整租）
                                for(Map<String,Object> conMap:InteDeviceList){
                                    //蜂电电表退租（如果是合租的租客）
                                    InteDeviceBeeUtil.deviceAmmeterConfirmrecederoom(conMap.get("Uuid").toString(),headMap);
                                }
                            }else if (params.get("ProOperaType").toString().equals("2")){
                                for(Map<String,Object> conMap:InteDeviceList){
                                    //智能设备UUID  模式0是后付费，1是预付费 请求头部信息
                                    //修改房间电表的付费模式
                                    InteDeviceBeeUtil.deviceAmmeterPaymode(conMap.get("Uuid").toString(),"1",headMap);
                                }
                            }
                        }
                    }
                    //去市场部修改合同的相关信息
                    JsonResult marketResult=zpcMktFeign.updatePactRent(params);
                    if (marketResult.get("errorCode")==null || !marketResult.get("errorCode").toString().equals("0")){
                        return result.put("服务器繁忙");
                    }
                    //微信推送--退租通知
                    Map<String, TemplateData> param = new HashMap<>();
                    param.put("first", new TemplateData("唐巢公寓温馨提示：尊敬的租客，退租提醒\n", "#4876FF"));
                    param.put("keyword1", new TemplateData(params.get("ComName").toString(), "#4876FF"));
                    param.put("keyword2", new TemplateData(params.get("Address").toString(), "#4876FF"));
                    param.put("keyword3", new TemplateData(params.get("updtm").toString(), "#4876FF"));
                    param.put("keyword4", new TemplateData(params.get("updtm").toString(), "#4876FF"));
                    Jsapi_ticketUtil.sendTemplate(params.get("openid").toString(), WeChatConfig.RENTPACT_ID,"http://www.4006269069.net/#/terminationDetail?PaId="+params.get("PaId"),"#4876FF", JSONObject.fromObject(param));
                    //修改账单为废弃
                    params.put("Source",params.get("PaId"));//账单来源编号
                    params.put("Status",4);//账单状态   1.待支付  2.支付完成  3待审核   4.账单废弃（租客违约）
                    params.put("delfg",1);//废弃标志位  0正常 1废弃
                    Integer hoCount=hoTenantBillMapper.updateHoStatusDelfg(params);
                    if (hoCount!=null){
                        result.putSuccess("操作成功");
                    }else{
                        result.putFailed("服务器繁忙");
                        TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                    }
                }else{
                    result.putFailed("服务器繁忙");
                    TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                }

            } catch (Exception e) {
                result.putFailed("服务器繁忙");
                e.printStackTrace();
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
            }
        }
        finally {
            lock.unlock();
        }
        return result;
    }
}
